﻿using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.Linq;
using System.Runtime.InteropServices;
using System.Text;
using System.Threading;
using System.Threading.Tasks;

namespace 打印进程中所有的线程名称
{
    //关键点
    //线程池的工作方式:
    //当你使用 ThreadPool.QueueUserWorkItem 方法时，线程池会从可用线程中选择一个线程来执行你的工作项。这个线程可能是一个新的线程，也可能是一个已经在执行其他工作项的线程。
    //由于线程池的线程是重用的，因此每次调用 DeviceInfoReUploadThread 时，实际执行该方法的线程可能是不同的。
    //System.AppDomain.GetCurrentThreadId():
    //System.AppDomain.GetCurrentThreadId() 返回的是当前执行线程的 ID。由于线程池中的线程是重用的，因此在不同的调用中，可能会使用不同的线程来执行 DeviceInfoReUploadThread，从而导致返回的线程 ID 可能会变化。
    //ThreadId 的值:
    //在你的代码中，ThreadId 是通过传递参数 i + 1 来设置的，因此在每个线程执行时，ThreadId 的值是固定的（1 到 5），但实际执行该方法的线程 ID 可能会变化。
    internal class Program
    {
        // 用于存储线程 ID 和名称的映射
        private static Dictionary<int, string> threadNames = new Dictionary<int, string>();

        static void Main()
        {
            ThreadPool.SetMinThreads(1000, 1000);
            ThreadPool.SetMaxThreads(1000, 1000);
            // 启动一些线程
            //for (int i = 0; i < 5; i++)
            //{
            //    // 创建线程并传递参数
            //    Thread thread = new Thread(new ParameterizedThreadStart(DoWork));
            //    thread.Start(i + 1);
            //}

            for (int i = 0; i < 5; i++)
            {               
                ThreadPool.QueueUserWorkItem(new WaitCallback(DeviceInfoReUploadThread),i  + 1);
            }

            // 等待一段时间以确保线程启动
            Thread.Sleep(1000);

            Task.Run(() =>
            {
                // 打印当前进程中的所有线程名称
                PrintThreadNames();
            });

            Console.ReadKey();
        }

        public static void DeviceInfoReUploadThread(object obj)
        {
            int ThreadId = (int)obj;
            string threadName = $"Thread111-{ThreadId}";
            threadNames.Add(System.AppDomain.GetCurrentThreadId(), threadName); // 存储线程名称
        }

        static void DoWork(object threadid)
        {
            int ThreadId = (int)threadid;
            string threadName = $"Thread-{ThreadId}";
            threadNames.Add(System.AppDomain.GetCurrentThreadId(), threadName); // 存储线程名称
            while (true)
            {
                Thread.Sleep(1000); // 模拟工作
            }
        }

        static void PrintThreadNames()
        {
            var currentProcess = Process.GetCurrentProcess();
            var threads = currentProcess.Threads;
            while (true)
            {
                foreach (ProcessThread processThread in threads)
                {
                    // 使用 ManagedThreadId 来获取线程名称
                    string threadName = threadNames.ContainsKey(processThread.Id) ? threadNames[processThread.Id] : "Unnamed";
                    Console.WriteLine($"Thread ID: {processThread.Id}, Thread Name: {threadName}");
                }
                Thread.Sleep(5000);
                Console.WriteLine($"------------------------------------------------------------");
            }
        }
    }
}
